﻿using FreeSql;
using Microsoft.Extensions.Logging;
using System;
using System.Linq;
using System.Threading.Tasks;
using Volo.Abp.Auditing;

namespace Colorful.Furniture.SysManagement;

/// <summary>
///  审计日志存储
/// </summary>
public class FurnitureDbAuditingLogStore : IAuditingStore
{
    private readonly IBaseRepository<SysApiLog> _sysApiLogRepository;
    private readonly ILogger<FurnitureDbAuditingLogStore> _logger;

    public FurnitureDbAuditingLogStore(
        IBaseRepository<SysApiLog> sysApiLogRepository,
        ILogger<FurnitureDbAuditingLogStore> logger)
    {
        _sysApiLogRepository = sysApiLogRepository;
        _logger = logger;
    }

    /// <summary>
    ///  保存审计日志
    /// </summary>
    /// <param name="auditInfo">审计信息</param>
    /// <returns></returns>
    /// <exception cref="System.NotImplementedException">未实现异常</exception>
    public async Task SaveAsync(AuditLogInfo auditInfo)
    {
        try
        {
            if (auditInfo.Actions.Any())
            {
                //审计日志的操作信息
                var actionInfo = auditInfo.Actions.FirstOrDefault();

                //TODO 通过解析XML将请求的方法直接写入中文
                var sysApi = new SysApiLog
                {
                    RequestUrl = auditInfo.Url,
                    AddTime = auditInfo.ExecutionTime,
                    Action = actionInfo?.MethodName,
                    Controller = actionInfo?.ServiceName,
                    RequestInput = actionInfo?.Parameters,
                    ElapsedMilliseconds = auditInfo.ExecutionDuration,
                    RequestMethod = auditInfo.HttpMethod,
                    Success = auditInfo.Exceptions.Count == 0,
                    ErrorMessage = auditInfo.Exceptions.FirstOrDefault()?.Message,
                    Browser = auditInfo.BrowserInfo,
                    Ip = auditInfo.ClientIpAddress,
                    OperatorId = auditInfo.UserId,
                    Operator = auditInfo.UserName,
                    Remark = string.Join(",", auditInfo.Comments),
                    AuditBody = auditInfo.ToString()
                };

                await _sysApiLogRepository.InsertAsync(sysApi);
            }
            else
            {
                _logger.LogInformation($"配置当前[{auditInfo.Url}]对应的action不进行审计日志记录");
            }

        }
        catch (Exception e)
        {
            _logger.LogError($@"插入审计日志错误:{e}");
        }

    }
}